﻿using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Drawing;
using System.Drawing.Drawing2D;

namespace zmMoniter
{
  
    class VibGraph
    {
        public int id;
        public string sFlag = "";
        public int type;
        public float fVibDepth;
        public float fVibAngle;
        public int iVibTime;
        public int iVibAllowDepth;
        public float fVibAllowAngle;
        public int iVibAllowMinTime;
        public int iVibAllowMaxTime;
        public int iVibQualified=0;
        public DateTime lastDate;
        public string sText;
        public string sValue;
        public Extent extent;
        public Pen pen;
        public SolidBrush opaqueBrush;
        public ArrayList alPoint = new ArrayList();
        public ArrayList alNewPoint = new ArrayList();
        public float fCenterX;
        public float fCenterY;
        public Font font;
        GraphicsPath myGraphicsPath;
        Region myRegion;
        bool bIsAddedPoint = false;
        public VibGraph(int iID, int iType)
        {
            id = iID;
            if (id == -1)
                lastDate = DateTime.Now;
            type = iType;
            extent = new Extent();
            sText = "";
            pen = new Pen(Color.Black, 1);
            font = null;
            sValue = "";
            opaqueBrush = null;
            sFlag = "";
            myGraphicsPath = new GraphicsPath();
            myRegion = new Region();
            myGraphicsPath.Reset();
        }
        public void setPos(float fX, float fY,float fAngle)
        {
            if (type != -1 && type != 1)
            {
                return;
            }
            fCenterX = fX;
            fCenterY = fY;
            fVibAngle = fAngle;
            
            for (int i = 0; i < alPoint.Count; i++)
            {
                Point pt = (Point)alPoint[i];
                alNewPoint[i] = angleTranslate(fCenterX, fCenterY, pt.dX, pt.dY, fVibAngle * Math.PI / 180);
            }
        }
        public void setParam(float fDepth,float fAngle,int iTime)
        {
            fVibDepth =fDepth;
            fVibAngle = fAngle;
            iVibTime = iTime;
        }
        public void setAllowParam(int iAllowDepth,float fAllowAngle, int fAllowMinTime, int fAllowMaxTime)
        {
            iVibAllowDepth = iAllowDepth;
            fVibAllowAngle = fAllowAngle;
            iVibAllowMinTime = fAllowMinTime;
            iVibAllowMaxTime = fAllowMaxTime;
        }
        public void setQualified(int iQualified)
        {
            iVibQualified = iQualified;
            if (iVibQualified != 0 && iVibQualified < iQualified)
                iVibQualified=iQualified;
            else if(iVibQualified == 0 )
                iVibQualified = iQualified;
        }
        public void setFlag(string flag)
        {
            sFlag = flag;
        }
        public void setPen(Pen p)
        {
            pen=p;
        }
        public void setPenStyle(System.Drawing.Drawing2D.DashStyle pStyle)
        {
            pen.DashStyle = pStyle;
        }
        public void setFont(Font ft)
        {
            font = ft;
        }
        public void setBrush(SolidBrush brush)
        {
            opaqueBrush = brush;
        }
        public void addValue(string value)
        {
            sValue = value;
        }
        public void addText(string sValue)
        {
            sText = sValue;
        }
        public void addPoint(Point pt,bool bIsPoint=true)
        {
            alPoint.Add(pt);
            if (type == -1 || type == 1)
            {
                alNewPoint.Add(pt);
            }
            if (bIsPoint)
                extent.upDate(pt);
        }
        public void upDatePoint(double dx, double dy, int index)
        {
            if (index >= alPoint.Count || index<0)
                return;
            Point pt = (Point)alPoint[index];
            pt.dX = dx;
            pt.dY = dy;
        }
        public Point getPoint(int index)
        {
            if(alPoint.Count>index&&index>=0)
            {

                return (Point)alPoint[index];
            }
            else
                return null;
        }
        public double getPointX(int index)
        {
            if (alPoint.Count > index && index >= 0)
            {
                return ((Point)alPoint[index]).dX;
            }
            else
                return -9999;
        }
        public double getPointY(int index)
        {
            if (alPoint.Count > index && index >= 0)
            {
                return ((Point)alPoint[index]).dY;
            }
            else
                return -9999;
        }
        public double getNewPointX(int index)
        {
            if (alNewPoint.Count > index && index >= 0)
            {
                return ((Point)alNewPoint[index]).dX;
            }
            else
                return -9999;
        }
        public double getNewPointY(int index)
        {
            if (alNewPoint.Count > index && index >= 0)
            {
                return ((Point)alNewPoint[index]).dY;
            }
            else
                return -9999;
        }
        public void setRegion()
        {
            if (alPoint.Count < 2)
                return ;

            Point pt1 = (Point)alPoint[0];
            Point ptn = (Point)alPoint[alPoint.Count - 1];
            if (!pt1.compare(ptn))
            {
                addPoint(pt1);
            }

            int iLength = alPoint.Count;
            System.Drawing.PointF[] pts = new System.Drawing.PointF[iLength];
            for (int j = 0; j < iLength; j++)
            {
                Point ptj = (Point)alPoint[j];
                pts[j] = new PointF((float)ptj.dX, (float)ptj.dY);
            }
            myGraphicsPath.AddPolygon(pts);
            myRegion.MakeEmpty();
            myRegion.Union(myGraphicsPath);
            bIsAddedPoint = true;
        }
        public double getDist(double dX, double dY)
        {
            double dMinDist = 999999999;
            int flag = -1;
            for (int p = 0; p < alPoint.Count; p++)
            {
                Point pt = (Point)alPoint[p];
                double dDist = pt.getLength(dX, dY);
                if (dMinDist > dDist)
                {
                    dMinDist = dDist;
                    flag = p;
                }
            }
            return dMinDist;
        }
        public bool IsIn(double ptX, double ptY, double dLength = 0.1)
        {
            bool bResult = false;
            if (!bIsAddedPoint)
            {
                return bResult;
            }
            if (!extent.inExtent(ptX, ptY))
            {
                return false;
            }
            if (IsPointInRegion(ptX , ptY ))
                return true;
            
            return bResult;
        }
        public bool IsPointInRegion(double dX, double dY)
        {
            PointF ptf = new PointF((float)dX, (float)dY);
            return myRegion.IsVisible(ptf);
        }
        private Point angleTranslate(double dfx, double dfy, double dx, double dy, double fAngle)
        {
            double sin = Math.Sin(fAngle);
            double cos = Math.Cos(fAngle);

            double x = dx * cos - dy * sin;
            double y = dx * sin + dy * cos;
            return new Point(dfx + x, dfy + y);
        }
    }
}
